#include "tarm_tim.h"

void TIM6_Init(void)
{
    // TMR6 clock enable
    RCC_APB1PeriphClockCmd(RCC_APB1PERIPH_TMR6, ENABLE);

    // TMRe base configuration
    TMR_TimerBaseInitType  TMR_TMReBaseStructure;
    TMR_TimeBaseStructInit(&TMR_TMReBaseStructure);
    TMR_TMReBaseStructure.TMR_Period = 65535;
    TMR_TMReBaseStructure.TMR_DIV = (uint16_t) 240-1;
    TMR_TMReBaseStructure.TMR_ClockDivision = TMR_CKD_DIV4;
    TMR_TMReBaseStructure.TMR_CounterMode = TMR_CounterDIR_Up;
    TMR_TimeBaseInit(TMR6, &TMR_TMReBaseStructure);
}

void TIM3_InitXUs(uint32_t inpu_timeUs)
{
    int t_divValue = inpu_timeUs>65535?100:10;
    inpu_timeUs = inpu_timeUs>65535?inpu_timeUs/10:inpu_timeUs;

    // TMR3 clock enable
    RCC_APB1PeriphClockCmd(RCC_APB1PERIPH_TMR3, ENABLE);

    NVIC_InitType NVIC_InitStructure;
    // Enable the TMR3 global Interrupt
    NVIC_InitStructure.NVIC_IRQChannel = TMR3_GLOBAL_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);

    // TMRe base configuration
    TMR_TimerBaseInitType  TMR_TMReBaseStructure;
    TMR_TimeBaseStructInit(&TMR_TMReBaseStructure);
    TMR_TMReBaseStructure.TMR_Period = 65535;
    TMR_TMReBaseStructure.TMR_DIV = (uint16_t) 24*t_divValue-1; //(SystemCoreClock / 10000) - 1;
    TMR_TMReBaseStructure.TMR_ClockDivision = TMR_CKD_DIV4;
    TMR_TMReBaseStructure.TMR_CounterMode = TMR_CounterDIR_Up;
    TMR_TimeBaseInit(TMR3, &TMR_TMReBaseStructure);


    // Output Compare Toggle Mode configuration: Channel1
    TMR_OCInitType  TMR_OCInitStructure;
    TMR_OCStructInit(&TMR_OCInitStructure);
    TMR_OCInitStructure.TMR_OCMode = TMR_OCMode_Active;
    TMR_OCInitStructure.TMR_OutputState = TMR_OutputState_Disable;
    TMR_OCInitStructure.TMR_Pulse = inpu_timeUs;
    TMR_OCInitStructure.TMR_OCPolarity = TMR_OCPolarity_Low;
    TMR_OC1Init(TMR3, &TMR_OCInitStructure);
    TMR_OC1PreloadConfig(TMR3, TMR_OCPreload_Disable);

    // TMR enable counter
    TMR_Cmd(TMR3, DISABLE);
    // TMR IT enable
    TMR_INTConfig(TMR3, TMR_INT_CC1, ENABLE);
}

void TIM3_Init(void)
{
    // TMR3 clock enable
    RCC_APB1PeriphClockCmd(RCC_APB1PERIPH_TMR3, ENABLE);

    NVIC_InitType NVIC_InitStructure;
    // Enable the TMR3 global Interrupt
    NVIC_InitStructure.NVIC_IRQChannel = TMR3_GLOBAL_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);

    // TMRe base configuration
    TMR_TimerBaseInitType  TMR_TMReBaseStructure;
    TMR_TimeBaseStructInit(&TMR_TMReBaseStructure);
    TMR_TMReBaseStructure.TMR_Period = 20000;
    TMR_TMReBaseStructure.TMR_DIV = (uint16_t) 240*25*4-1; //(SystemCoreClock / 10000) - 1;
    TMR_TMReBaseStructure.TMR_ClockDivision = TMR_CKD_DIV4;
    TMR_TMReBaseStructure.TMR_CounterMode = TMR_CounterDIR_Up;
    TMR_TimeBaseInit(TMR3, &TMR_TMReBaseStructure);


    // Output Compare Toggle Mode configuration: Channel1
    TMR_OCInitType  TMR_OCInitStructure;
    TMR_OCStructInit(&TMR_OCInitStructure);
    TMR_OCInitStructure.TMR_OCMode = TMR_OCMode_Active;
    TMR_OCInitStructure.TMR_OutputState = TMR_OutputState_Disable;
    TMR_OCInitStructure.TMR_Pulse = 10000;
    TMR_OCInitStructure.TMR_OCPolarity = TMR_OCPolarity_Low;
    TMR_OC1Init(TMR3, &TMR_OCInitStructure);
    TMR_OC1PreloadConfig(TMR3, TMR_OCPreload_Disable);

    // TMR enable counter
    TMR_Cmd(TMR3, ENABLE);
    // TMR IT enable
    TMR_INTConfig(TMR3, TMR_INT_CC1 | TMR_INT_Overflow, ENABLE);
}

//void TIM3_ChangeMatchValue(uint32_t i_timeUs)
//{
//    TIM3_InitXUs(i_timeUs);
//}

void TIM4C4_PWM(void)
{
    RCC_APB2PeriphClockCmd(RCC_APB2PERIPH_GPIOD|RCC_APB2PERIPH_AFIO, ENABLE);
    GPIO_PinsRemapConfig(GPIO_Remap_TMR4,ENABLE);
    GPIO_InitType GPIO_InitStructure = {0};

    /* GPIOA Configuration: Channel 1, 2 and 3 as alternate function push-pull */
    GPIO_StructInit(&GPIO_InitStructure);
    GPIO_InitStructure.GPIO_Pins = GPIO_Pins_12;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
    GPIO_InitStructure.GPIO_MaxSpeed = GPIO_MaxSpeed_50MHz;
    GPIO_Init(GPIOD, &GPIO_InitStructure);

    // TMR4 clock enable
    RCC_APB1PeriphClockCmd(RCC_APB1PERIPH_TMR4, ENABLE);
    // TMRe base configuration
    TMR_TimerBaseInitType  TMR_TMReBaseStructure;
    TMR_TimeBaseStructInit(&TMR_TMReBaseStructure);
    TMR_TMReBaseStructure.TMR_Period = 20000;
    TMR_TMReBaseStructure.TMR_DIV = (uint16_t) 240-1; //(SystemCoreClock / 10000) - 1;
    TMR_TMReBaseStructure.TMR_ClockDivision = TMR_CKD_DIV4;
    TMR_TMReBaseStructure.TMR_CounterMode = TMR_CounterDIR_Up;
    TMR_TimeBaseInit(TMR4, &TMR_TMReBaseStructure);

    // Output Compare Toggle Mode configuration: Channel1
    TMR_OCInitType  TMR_OCInitStructure;
    TMR_OCStructInit(&TMR_OCInitStructure);
    TMR_OCInitStructure.TMR_OCMode = TMR_OCMode_PWM2;
    TMR_OCInitStructure.TMR_OutputState = TMR_OutputState_Enable;
    TMR_OCInitStructure.TMR_Pulse = 200;
    TMR_OCInitStructure.TMR_OCPolarity = TMR_OCPolarity_Low;
    TMR_OC1Init(TMR4, &TMR_OCInitStructure);
    TMR_OC1PreloadConfig(TMR4, TMR_OCPreload_Enable);

    TMR_Cmd(TMR4, ENABLE);
    TMR_CtrlPWMOutputs(TMR4, ENABLE);
}


//void TIM4C4_PWMChangeValue(uint32_t value)
//{
//    TMR_SetCompare3(TMR4, value);
//}

void TIM5_InitXUs(uint32_t inpu_timeUs)
{
    int t_divValue = inpu_timeUs>65535?100:10;
    inpu_timeUs = inpu_timeUs>65535?inpu_timeUs/10:inpu_timeUs;

    // TMR3 clock enable
    RCC_APB1PeriphClockCmd(RCC_APB1PERIPH_TMR5, ENABLE);

    NVIC_InitType NVIC_InitStructure;
    // Enable the TMR5 global Interrupt
    NVIC_InitStructure.NVIC_IRQChannel = TMR5_GLOBAL_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);

    // TMRe base configuration
    TMR_TimerBaseInitType  TMR_TMReBaseStructure;
    TMR_TimeBaseStructInit(&TMR_TMReBaseStructure);
    TMR_TMReBaseStructure.TMR_Period = 65535;
    TMR_TMReBaseStructure.TMR_DIV = (uint16_t) 24*t_divValue-1; //(SystemCoreClock / 10000) - 1;
    TMR_TMReBaseStructure.TMR_ClockDivision = TMR_CKD_DIV4;
    TMR_TMReBaseStructure.TMR_CounterMode = TMR_CounterDIR_Up;
    TMR_TimeBaseInit(TMR5, &TMR_TMReBaseStructure);


    // Output Compare Toggle Mode configuration: Channel1
    TMR_OCInitType  TMR_OCInitStructure;
    TMR_OCStructInit(&TMR_OCInitStructure);
    TMR_OCInitStructure.TMR_OCMode = TMR_OCMode_Active;
    TMR_OCInitStructure.TMR_OutputState = TMR_OutputState_Disable;
    TMR_OCInitStructure.TMR_Pulse = inpu_timeUs;
    TMR_OCInitStructure.TMR_OCPolarity = TMR_OCPolarity_Low;
    TMR_OC1Init(TMR5, &TMR_OCInitStructure);
    TMR_OC1PreloadConfig(TMR5, TMR_OCPreload_Disable);

    // TMR enable counter
    TMR_Cmd(TMR5, DISABLE);
    // TMR IT enable
    TMR_INTConfig(TMR5, TMR_INT_CC1, ENABLE);
}


void TMR3_GLOBAL_IRQHandler(void)
{
    if (TMR_GetINTStatus(TMR3, TMR_INT_CC1) != RESET)
    {
      TMR_ClearITPendingBit(TMR3, TMR_INT_CC1 );
//      capture = TMR_GetCapture1(TMR3);
//      TMR_SetCompare1(TMR3, capture + 32768 );
      Time1CallBack();
      TMR3->CNT = 0;
//      AT32_LEDn_Toggle(LED3);
    }
    if (TMR_GetINTStatus(TMR3, TMR_INT_Overflow) != RESET)
    {
      TMR_ClearITPendingBit(TMR3, TMR_INT_Overflow );
//      AT32_LEDn_Toggle(LED4);
    }
}


void TMR5_GLOBAL_IRQHandler(void)
{
    if (TMR_GetINTStatus(TMR5, TMR_INT_CC1) != RESET)
    {
      TMR_ClearITPendingBit(TMR5, TMR_INT_CC1 );
      Time0CallBack();
      TMR5->CNT = 0;
//      AT32_LEDn_Toggle(LED3);
    }
    if (TMR_GetINTStatus(TMR5, TMR_INT_Overflow) != RESET)
    {
      TMR_ClearITPendingBit(TMR5, TMR_INT_Overflow );
//      AT32_LEDn_Toggle(LED4);
    }
}
